16.3. 条件和循环
表 1 显示,C 和 Java 中 if
- else
语句的语法和语义相同。
表 1. Java 和 C 中 if-else 语句的语法比较
Java version | C version |
---|---|
|
|
Java 和 C 中 if
-else
语句的语法相同。在两者中,else
部分都是可选的。Java 和 C 还通过链接 if
和 else if
语句支持多路分支。以下描述了完整的 if
-else
C 语法:
// a one-way branch:
if ( <boolean expression> ) {
<true body>
}
// a two-way branch:
if ( <boolean expression> ) {
<true body>
}
else {
<false body>
}
// a multibranch (chaining if-else if-...-else)
// (has one or more 'else if' following the first if):
if ( <boolean expression 1> ) {
<true body>
}
else if ( <boolean expression 2> ) {
// first expression is false, second is true
<true 2 body>
}
else if ( <boolean expression 3> ) {
// first and second expressions are false, third is true
<true 3 body>
}
// ... more else if's ...
else if ( <boolean expression N> ) {
// first N-1 expressions are false, Nth is true
<true N body>
}
else { // the final else part is optional
// if all previous expressions are false
<false body>
}
16.3.1. C 语言中的布尔值
C 不提供具有真或假值的布尔类型。相反,整数值在条件语句中使用时计算结果为 true 或 false。在条件表达式中使用时,任何整数表达式:
- 零 (0) 计算结果为 false
- 非零(任何正值或负值) 计算结果为 真
C 有一组用于布尔表达式的关系运算符和逻辑运算符,与 Java 的关系运算符和逻辑运算符相同。
关系运算符 采用相同类型的操作数,并计算结果为零(假)或非零(真)。关系运算符集包括:
- 相等(
==
)和不等(不等,!=
) - 比较运算符:小于(
<
)、小于或等于(<=
)、大于(>
)和大于或等于(>=
)
以下是一些显示关系运算符示例的 C 代码片段:
// assume x and y are ints, and have been assigned
// values before this point in the code
if (y < 0) {
printf("y is negative\n");
} else if (y != 0) {
printf("y is positive\n");
} else {
printf("y is zero\n");
}
// set x and y to the larger of the two values
if (x >= y) {
y = x;
} else {
x = y;
}
C 的 逻辑运算符 采用整数“布尔”操作数,其计算结果为零(假)或非零(真)。逻辑运算符集包括:
- 逻辑否定(
!
) - 逻辑与(
&&
):在第一个错误表达式处停止评估(短路) - 逻辑或(
||
):在第一个真表达式处停止评估(短路)
C 的 短路 逻辑运算符求值在知道结果后立即停止求值逻辑表达式。例如,如果逻辑与(&&
)表达式的第一个操作数求值为假,则 &&
表达式的结果必定为假。因此,第二个操作数的值不需要求值,也不会被求值。
以下是 C 语言中使用逻辑运算符的条件语句的示例(最好在复杂的布尔表达式周围使用括号以使其更易于阅读):
if ( (x > 10) && (y >= x) ) {
printf("y and x are both larger than 10\n");
x = 13;
} else if ( ((-x) == 10) || (y > x) ) {
printf("y might be bigger than x\n");
x = y * x;
} else {
printf("I have no idea what the relationship between x and y is\n");
}
16.3.2. C 中的循环
Java 和 C 都具有对重复代码序列的语言级别支持。与 Java 一样,C 也支持 for
、while
和 do
-while
循环。这两种语言的语法和语义相同。Java 还支持对集合进行迭代,而 C 则不支持。
while循环
C 和 Java 中的 while
循环语法相同,行为也相同。表 2 显示了带有 while
循环的示例 C 程序。
表 2. C 语言中的 while 循环语法
C while loop example |
---|
|
C 中的 while
循环语法与 Java 中的相同,并且都以相同的方式进行评估:
while ( <boolean expression> ) {
<true body>
}
while
循环首先检查布尔表达式,如果为真则执行循环体。在上面的示例程序中,val
变量的值将在 while
循环中重复打印,直到其值大于 num
变量的值。如果用户输入 10
,C 和 Java 程序将打印:
1
2
4
8
Java 和 C 也有一个 do
-while
循环,它与 while
循环类似,但它首先执行循环体,然后检查条件,只要条件为真,就重复执行循环体。也就是说,do
-while
循环总是会执行循环体至少一次:
do {
<body>
} while ( <boolean expression> );
要获取更多 while
循环示例,请尝试以下两个程序:
for循环
C 中的 for
循环与 Java 中的 for
循环相同,并且它们的评估方式相同。C(和 Java)for
循环语法为:
for ( <initialization>; <boolean expression>; <step> ) {
<body>
}
for
循环评估规则是:
- 第一次进入循环时,评估一次 initialization。
- 计算布尔表达式的值。如果为 0(假),则退出
for
循环(即程序已完成重复循环体语句)。 - 评估循环主体内(body)的语句。
- 评估 step 表达式。
- 从步骤(2)开始重复。
这是一个简单的示例 for
循环,用于打印值 0、1 和 2:
int i;
for (i = 0; i < 3; i++) {
printf("%d\n", i);
}
在前面的循环中执行 for
循环评估规则会产生以下操作序列:
(1) eval init: i is set to 0 (i=0)
(2) eval bool expr: i < 3 is true
(3) execute loop body: print the value of i (0)
(4) eval step: i is set to 1 (i++)
(2) eval bool expr: i < 3 is true
(3) execute loop body: print the value of i (1)
(4) eval step: i is set to 2 (i++)
(2) eval bool expr: i < 3 is true
(3) execute loop body: print the value of i (2)
(4) eval step: i is set to 3 (i++)
(2) eval bool expr: i < 3 is false, drop out of the for loop
以下程序展示了一个更为复杂的 for
循环示例(也可以下载)。请注意,仅仅因为 C 支持 for
循环,并且其 初始化 和 单步步骤 部分都有一串语句,所以最好保持简单(此示例说明了一个更为复杂的 for
循环语法,但如果通过将 j += 10
步骤语句移到循环体末尾并只包含一个步骤语句 i += 1
来简化 for
循环,它将更易于阅读和理解)。
/* An example of a more complex for loop which uses multiple variables.
* (it is unusual to have for loops with multiple statements in the
* init and step parts, but C supports it and there are times when it
* is useful...don't go nuts with this just because you can)
*/
#include <stdio.h>
int main(void) {
int i, j;
for (i=0, j=0; i < 10; i+=1, j+=10) {
printf("i+j = %d\n", i+j);
}
return 0;
}
// the rules for evaluating a for loop are the same no matter how
// simple or complex each part is:
// (1) evaluate the initialization statements once on the first
// evaluation of the for loop: i=0 and j=0
// (2) evaluate the boolean condition: i < 10
// if false (when i is 10), drop out of the for loop
// (3) execute the statements inside the for loop body: printf
// (4) evaluate the step statements: i += 1, j += 10
// (5) repeat, starting at step (2)
与 Java 一样,C 中的 for
循环和 while
循环的功能是等效的,这意味着任何 while
循环都可以表示为 for
循环,反之亦然。
考虑 C 语言中的以下 while
循环:
int guess = 0;
while (guess != num) {
printf("%d is not the right number\n", guess);
printf("Enter another guess: ");
scanf("%d", &guess);
}
这个循环可以转换为 C 语言中等效的for
循环:
int guess;
for (guess = 0; guess != num; ) {
printf("%d is not the right number\n", guess);
printf("Enter another guess: ");
scanf("%d", &guess);
}
由于 for
和 while
循环在 C 语言中表达能力相同,因此该语言只需要一个循环结构。但是,for
循环对于确定性循环(如迭代一系列值)来说是一种更自然的语言结构,而 while
循环对于不确定循环(如重复直到用户输入偶数)来说是一种更自然的语言结构。因此,C(和 Java)为程序员提供了这两种语言结构。